package real.lang.reflect;

import java.util.*;
import java.lang.StringBuilder;

import real.lang.RealLangException;

public class CommonRealType extends AbstractRealType {

	private RealTypeSignature signature;

	public EnumerationOfRealTypes getRealTypeEnum() {
		return this.signature.getRealTypeEnum();
	}

	public Set<EnumerationOfRealSubtypes> getRealSubtypesEnum() {
		return this.signature.getRealSubtypesEnum();
	}

	public RealTypeSignature getSignature() {
		return null;
	}

	CommonRealType(RealTypeSignature signature, Class<?> real) {
		super(real);
		this.signature = signature;
	}

	public boolean HasSubTypes() {
		return (this.signature.getRealSubtypesEnum().size() > 0);
	}

	public boolean HasSiblings() throws RealLangException {
		if (!this.HasSuperType())
			return false;
		Collection<RealType> superTypes = this.getSuperRealTypes();
		boolean siblings = false;
		for (RealType realType : superTypes) {
			if (realType.getSubRealTypes().size() > 1) {
				siblings = true;
				break;
			}
		}
		return siblings;
	}

	public boolean HasSuperType() throws RealLangException {
		return (this.getSuperRealTypes() != null && this.getSuperRealTypes()
				.size() > 0);
	}

	public String getName() {
		StringBuilder sb = new StringBuilder();
		for (EnumerationOfRealSubtypes subtype : this.signature
				.getRealSubtypesEnum()) {
			sb.append(subtype.name());
		}
		sb.append(this.signature.getRealTypeEnum().name());
		return sb.toString();
	}

	public boolean IsTypeOf(EnumerationOfRealTypes type) {
		return (this.signature.getRealTypeEnum() == type);
	}

	public boolean IsTypeOf(RealType type) {
		return this.equals(type);
	}

	/**
	 * This method takes use of isSubtype relation from RTI
	 * 
	 * @throws RealLangException
	 */
	public Collection<RealType> getSubRealTypes() throws RealLangException {
		RealTypeRelation isSubtupe = RealRTI.getInstance().GetSubtypeRelation(
				this.signature.getTypeSpace());
		Collection<RealType> types = RealRTI.getInstance().getTypes();
		List<RealType> result = new ArrayList<RealType>();
		for (RealType realType : types) {
			if (isSubtupe.contains(realType,this)) // realType is subtype of this
				result.add(realType);
		}
		return result;
	}

	/**
	 * This method takes use of isSubtype relation from RTI
	 * @throws RealLangException 
	 */
	public Collection<RealType> getSuperRealTypes() throws RealLangException {
		RealTypeRelation isSubtupe = RealRTI.getInstance().GetSubtypeRelation(
				this.signature.getTypeSpace());
		Collection<RealType> types = RealRTI.getInstance().getTypes();
		List<RealType> result = new ArrayList<RealType>();
		for (RealType realType : types) {
			if (isSubtupe.contains(this,realType)) // this is subtype of realType
				result.add(realType);
		}
		return result;
	}

}
